TITL DAI FIRMWARE C000-C1FA V1.0 Rev.1 ORG :C000 * * * * ================= *** MATH. UTILITIES *** * ================= * * *************** * ENTRYPOINTS * *************** * BASE JMP :C719 Reset (entry on hardware REM reset) XINIT JMP :C035 Math. package initialisation XFINM JMP :C0F3 Incr. FPT number in memory XFDCM JMP :C1FB Decr. FPT number in memory REM (not used) XFCOMP JMP :C079 FPT Compare XIINM JMP :C0BB Incr. INT number in memory XIDCM JMP :C0D5 Decr. INT number in memory REM (not used) XICOMP JMP :C0AC INT Compare XPUSH JMP :C21E Save MACC on stack XPOP JMP :C234 Retrieve MACC from stack XFCB JMP :C249 Input FPT number to MACC XFBC JMP :C361 Conv. FPT number for output XICB JMP :C573 Input INT number to MACC XIBC JMP :C5B2 Conv. INT number for output XHCB JMP :C614 Input Hex number to MACC XHBC JMP :C653 Conv. MACC to Hex for output XPRTY JMP :C486 Pretties up FPT/INT number DECBUF DBL :00E3 Location output buffer * ******************************** * MATH. PACKAGE INITIALISATION * ******************************** * * Entry: HL: Address input encoding routine (DDE0). * DE: Base address error routines (C7F2). * Exit: AFDEHL corrupted, BC preserved. * MINIT SHLD :00D2 Init. (00D2/3)=DDE0 XCHG SHLD :00D0 Init. (00D0/1)=C7F2 LDA :FB02 Get math.chip status ORA A Check if math.chip present MVI A,:00 Flag = 0 if not JM :C047 MVI A,:7B Flag = #7B if present LC18 STA :00D4 Set math.chip flag RET * ************************** * OVERFLOW ERROR ROUTINE * ************************** * * (From LC20 common part for various entries). * * Jump to (00D0/1) = Address 'overflow error' * routine (C7F2). * * Entry: If start at LC20: offset in HL. * Exit: AFBCDEHL preserved. * On stack original returnaddress. * FPEOV PUSH H LXI H,:0000 Init offset = 0 * LC20 PUSH PSW PUSH D XCHG Offset in DE LHLD :00D0 Get addr pointer DAD D Add offset MOV A,M INX H MOV H,M MOV L,A Get addr routine in HL POP D POP PSW XTHL New addr on stack RET Continu with new address * ****************** * ARGUMENT ERROR * ****************** * * Jump to (00D0/1)+2 = Address 'number out of range' * routine (C7F4). * * Entry/exit: See FPEOV. * FPEAE PUSH H LXI H,:0002 Init. offset JMP :C04F Calc. new addr, go to it * ******************* * UNDERFLOW ERROR * ******************* * * Jump to (00D0/1)+4 = Return (C7F6). * Underflow gives 0 as result of operation. * * Entry/exit: See FPEOV. * FPEUN PUSH H LXI H,:C45E Addr. FPT(0) JMP :D20C Copy '0' into MACC * ************************ * DIVIDE BY ZERO ERROR * ************************ * * Jump to (00D0/1)+6 = Address 'divide by zero' * routine (C7F8). * * Entry/exit: See FPEOV. * FPED0 PUSH H LXI H,:0006 Init. offset JMP :C04F Calc. new addr, go to it * * *************************** * GET CHARACTER FROM LINE * *************************** * * Entry: None. * Exit : All registers preserved. * Address to continue on stack. * LC22 PUSH H LHLD :00D2 Get addr 'Get char' routine XTHL on stack; restore HL RET Goto (00D0/1)+2 * ************************** * FLOATING POINT COMPARE * ************************** * * Compares normalised FPT numbers in MACC * and in M. * * Exit: ABCDEHL preserved. * Flags: CY=1,S=0,Z=1: both nrs. 0 * CY=0,S=0,Z=1: both nrs. identical * CY=0,S=0,Z=0: MACC > M * CY=0,S=1,Z=0: MACC < M * FCOMP PUSH B PUSH PSW PUSH D PUSH H RST 4 Copy MACC to reg A,B,C,D DATA :15 MOV E,A Exp.byte in E XRA M XOR both exp.bytes JM :C0B7 Jump if different signs REM * If equal signs: REM JMP :D1E8 Goto D1E8, return to C087 * LC23 RAL JNZ :C0A3 LC24 MOV A,E SUB M Comp. exp. bytes JNZ :C0A2 Jump if not equal INX H MOV A,B SUB M Comp. 1st bytes mantissa's JNZ :C0A2 Jump if not equal INX H MOV A,C SUB M Comp. 2nd bytes mantissa's JNZ :C0A2 Jump if not equal INX H MOV A,D SUB M Comp. 3rd bytes mantissa's LC25 JZ :C0A6 Jump if not equal LC26 RAR ) Set flags for output LC27 XRA E ) LC28 ORI :01 Clear CY-flag LC29 POP H POP D POP B MOV A,B Restore A POP B RET * ******************* * INTEGER COMPARE * ******************* * * Compares INT numbers in MACC and M. * REMARK: Routine is incorrect when both * numbers are negative ! Then result * is if MACC > M due to LC26/LC27. * * Exit: ABCDEHL preserved. CY=0 * Flags: S=0, Z=1: Both numbers equal * S=0, Z=0: MACC > M * S=1, Z=0: MACC < M * ICOMP PUSH B PUSH PSW PUSH D PUSH H RST 4 Copy MACC to reg. A,B,C,D DATA :15 MOV E,A Sign byte in E XRA M XOR both sign bytes JP :C08B If both nrs have same sign: REM compare REM * If different signs: REM LC241 XRA M Find out which one is neg: REM S=1: MEM pos; MACC neg REM S=0: MEM neg; MACC pos JMP :C0A4 Abort * ************************************** * INCREMENT INTEGER NUMBER IN MEMORY * ************************************** * * Entry: HL points to 1st byte of INT number. * Exit: All registers preserved. * IINM PUSH PSW PUSH H INX H INX H INX H HL pnts to last byte MVI A,:03 Nr of bytes for INT nr LC30 INR M Incr. INT nr. JNZ :C0D2 Ready if no overflow DCX H Goto next byte DCR A 1st byte reached? JNZ :C0C2 Incr. next byte INR M Incr. 1st byte MOV A,M Get it CPI :80 msb=1? CZ :C04B Then overflow error LC31 POP H Normal return POP PSW RET * *************************************************** * DECREMENT INTEGER NUMBER IN MEMORY - (not used) * *************************************************** * * Entry: HL points to 1st byte of INT number. * Exit: All registers preserved. * IDCM PUSH PSW PUSH B PUSH H INX H INX H INX H HL pnts to last byte MVI B,:03 Nr. of bytes of INT nr. LC32 DCR M Decr. INT nr MOV A,M INR A Check for overflow JNZ :C0EF Ready if no overflow DCX H Goto next byte DCR B Decr. byte count JNZ :C0DD Next byte if not ready DCR M Decr. hibyte MOV A,M CPI :7F Check for overflow CZ :C04B Then run overflow error LC33 POP H Normal return POP B POP PSW RET * ********************************************* * INCREMENT FLOATING POINT NUMBER IN MEMORY * ********************************************* * * If number = 0, or exponent < 0, a '1' is added * to the lsb of the mantissa. Else, the position * of the least significant '1' is looked up, and * a '1' is added to this position. * If the lsb of the mantissa is already a rounded * value, no increment occurs. * * Entry: HL points to 1st byte of FPT number. * Exit: All registers preserved. * FINM PUSH PSW PUSH B PUSH D PUSH H LXI D,:C462 Addr FPT(1) MOV A,M Get exp.byte ANI :7F Mask sign bit JZ :C1AC If nr=0: add 1, abort CPI :40 Is exponent negative? JNC :C1AC Then add 1, abort CPI :19 Lsb of mantissa is not lsb REM of number ? JNC :C14D Then Popall, ret CMP M Check if nr. is negative INX H JNZ :C152 Then jump REM * From LC34 also used by XFDCM. * Find lsb of mantissa if nr is positive: REM LC34 SUI :09 In 1st byte ? CC :C1EE Then SHL bit into A (A) time JC :C136 and jump INX H SUI :08 In 2nd byte ? CC :C1EE Then SHL bit into A (A) time JC :C12E and jump INX H SUI :08 In 3rd byte ? CALL :C1EE Then SHL bit into A (A) time ADD M MOV M,A Add 1 to 3rd byte mantissa JNC :C14D Ready if no overflow DCX H MVI A,:01 Overflow: add 1 to 2nd byte LC35 ADD M MOV M,A Add 1 to 2nd byte mantissa JNC :C14D Ready if no overflow DCX H MVI A,:01 Overflow: add 1 to 1st byte LC36 ADD M MOV M,A Add 1 to 1st byte mantissa JNC :C14D Ready if no overflow REM * If overflow into exponent byte: REM RAR ) MOV M,A ) INX H ) MOV A,M ) Shift all bits in RAR ) mantissa right MOV M,A ) one position INX H ) MOV A,M ) RAR ) MOV M,A ) DCX H DCX H DCX H HL pnts to exp.byte MVI A,:01 LC37 CALL :C1BA Add 1 to exponent * EXIT POP H POP D POP B POP PSW RET REM * Find lsb of mantissa if nr is negative: REM LC39 SUI :09 In 1st byte ? CC :C1EE Then SHL bit into A (A) time JC :C17D and jump INX H SUI :08 In 2nd byte ? CC :C1EE Then SHL bit into A (A) time JC :C173 and jump INX H SUI :08 In 3rd byte ? CC :C1EE Then SHL bit into A (A) time MOV B,A MOV A,M SUB B Subtract 1 from 3rd byte MOV M,A JNC :C14D Ready if no borrow DCX H MVI A,:01 Subtract 1 from 2nd byte if REM borrow LC40 MOV B,A MOV A,M SUB B Subtract 1 from 2nd byte MOV M,A JNC :C14D Ready if no borrow DCX H MVI A,:01 Subtract 1 from 1st byte if REM borrow LC41 MOV B,A MOV A,M SUB B Subtract 1 from 1st byte MOV M,A JM :C14D Ready if normalised REM * If not normalised: REM MVI B,:18 Nr of mantissa bits LC42 INX H ) INX H ) ORA A ) MOV A,M ) RAL ) MOV M,A ) Shift all bits DCX H ) of mantissa MOV A,M ) left one position RAL ) MOV M,A ) DCX H ) MOV A,M ) RAL ) MOV M,A ) ORA A JM :C19F If normalized DCR B Update exp. count JZ :C1A6 If exp. now zero JMP :C186 Cont. normalisation REM * Normalisation done: REM LC43 DCX H Pnts to exp.byte MOV A,B Get exp. count SUI :19 Minus nr of bytes in REM mantissa JMP :C14A Update exponent, quit REM * If exponent is zero: REM LC44 DCX H MVI M,:00 Exp.byte is 0 JMP :C14D Popall, ret REM * Simply add 1 (FINM) or add -1 (FDCM): REM LC45 RST 4 Copy number into MACC DATA :0C XCHG RST 4 Add 1 or -1 (FPT) DATA :00 XCHG RST 4 Copy MACC into memory DATA :0F JMP :C14D Popall, ret * ***************** * ADD EXPONENTS * ***************** * * LC225 for operand in MACC. * LC46 for operand in M. * * Entry: Byte to be added to exponent in A. * Exit: BCDEHL preserved. * CY=0: O.K. * CY=1: Overflow. * LC225 LXI H,:00D5 Addr. MACC * LC46 PUSH H PUSH D PUSH B MOV C,A Byte to be added in C MOV A,M Get exp.byte operand ANI :80 Sign bit mantissa only MOV B,A in B MOV A,M Get exp.byte CALL :C1E9 Sign extend PUSH PSW Save sign extended exp.byte XRA C XOR with byte to be added CMA MOV D,A POP PSW Get sign extended exp.byte ADD C Add byte to exponent MOV C,A Store result RAR XRA C ANA D JM :C1E2 If overflow into sign bit MOV A,C Get new exp.byte RAL XRA C JM :C1E2 If overflow into sign bit MOV A,C Get new exp.byte ANI :7F Exponent only ORA B Add sign bit mantissa MOV M,A Store it LC47 POP B POP D POP H RET CY=0 REM * If overflow into sign bit: REM LC48 MOV A,C Get new exp.byte RAL ORA A STC JMP :C1DE Abort with CY=1 * *************** * SIGN EXTEND * *************** * * Exponent byte is normalized. * * Entry: Exp.byte in A. * Exit: BCDEHL preserved. * Normalized exp.byte in A: Exp.value in * bits 7-2, sign mantissa in bit 1, sign * exponent in bit 0. * SEXT RLC RLC RRC RAR RET * ************************************ * MOVE A BIT INTO A LEFT (A) TIMES * ************************************ * * Used to place a '1' in the correct position in * a byte for adding/subtracting '1' to/from the * least significant '1' of a FPT mantissa. * * Entry: A contains a neg. number indicating * how often RAL has to be performed. * Exit: Result in A,B. * FCDEHL preserved. * LC50 PUSH PSW MOV B,A Save nr of shifts XRA A Clear A STC Set CY LC51 RAL SHL INR B Update count JNZ :C1F2 Continu if not ready MOV B,A Save result POP PSW MOV A,B Result in A RET * * * END